Wednesday, 6 May 2015

Dynamic Xquery Transformations in OSB


Dynamic transformations allow you to define a proxy service which can handle new transformations being added at a later date.Let's look at how we might implement a typical scenario where a proxy service accepts multiple versions of a message and applies an appropriate transformation based on the version of the message.

Goal:
In this POC Iam having 3 XQ Transformations for calling this i made one RuleSet which will helpfull for calling my Xquery transformations based open my input.My task is to Call Dynamically these 3 Xquery transformations based upon the Operation input given from input proxy data.

First create a new Oracle Service Bus project and name it as DynamicXqueryPOC (File>New>Oracle Service Bus Project, enter a name of DynamicXqueryPOC and click Finish).
In the main editor pane, select the General tab for this service and make sure it is defined as a Messaging Service.Now move to the Messaging tab,set the Request and Response Type to XML.Go the  Message flow tab and take the pipeline-pair and put the stage inside to create a logic.Drag a Assign activity under the Stage and give $body/* into expression and assign to Request variable.

For passing the data to the below xquery take two assign activity to capture element1 and element2 and pass this data to the below xquery.

Xquery will accept the 2 input strings
xquery version "1.0" encoding "Cp1252";
declare namespace xf = "http://tempuri.org/DynamicPOC/Resources/Version/";
declare function xf:Version($string1 as xs:string,
    $string2 as xs:string)
    as xs:string {
        concat($string1,$string2,'VersionCalled')
};

declare variable $string1 as xs:string external;
declare variable $string2 as xs:string external;

xf:Version($string1,
    $string2)

Create 3 Xquery's with simple concat operations like below and name the xquery transformations as Version.xq,Version1.xq and Version2.xq.

Create RoutingRule xquery transformation for mention the rules and getServicesXQ is for calling the dynamic xquery's Version,Version1 and Version2 based upon the Operation
1.RoutingRule.xq
<Rules>
  <Operations>
    <Operation Name="Operation1">
      <RoutingRules>
        <RoutingRule>
          <Transformation>
            <XQ Name="Case1_XQ"/>
          </Transformation>
        </RoutingRule>
      </RoutingRules>
    </Operation>
    <Operation Name="Operation2">
      <RoutingRules>
        <RoutingRule>
          <Transformation>
            <XQ Name="Case2_XQ"/>
          </Transformation>
        </RoutingRule>
      </RoutingRules>
    </Operation>
    <Operation Name="Operation3">
      <RoutingRules>
        <RoutingRule>
          <Transformation>
            <XQ Name="Case3_XQ"/>
          </Transformation>
        </RoutingRule>
      </RoutingRules>
    </Operation>
  </Operations>
  <RoutingServices>
    <RoutingXQ Name="Case1_XQ">
      <Address>DynamicPOC/Resources/Version</Address>
    </RoutingXQ>
    <RoutingXQ Name="Case2_XQ">
      <Address>DynamicPOC/Resources/Version1</Address>
    </RoutingXQ>
    <RoutingXQ Name="Case3_XQ">
      <Address>DynamicPOC/Resources/Version2</Address>
    </RoutingXQ>
  </RoutingServices>
</Rules>
Take this above Xquery in assign activity and map to the routingRules variable.

getServicesXQ.xq
xquery version "1.0" encoding "Cp1252";
(:: pragma  parameter="$Rules" type="xs:anyType" ::)
(:: pragma  parameter="$Operation" type="xs:anyType" ::)
(:: pragma  type="xs:string" ::)
declare namespace xf = "http://tempuri.org/Examples/GetRoutingXQ";
declare function xf:getServicesXQ($Rules as element(*), $Operation as xs:string)
as xs:string {
let $Result := for $Rule in $Rules//Operations/Operation[@Name= $Operation]/RoutingRules/*
let $TransXQOperation:= $Rule/Transformation/XQ/@Name
for $RoutingAddress in $Rules//RoutingServices/RoutingXQ[@Name = $TransXQOperation]/Address
return $RoutingAddress
return data($Result)
};
declare variable $Rules as element(*) external;
declare variable $Operation as xs:string external;
xf:getServicesXQ($Rules,$Operation)

Take this into assign activity and pass the input's routingRules and Operation variable and name it as dynaXQ like below.



This query will helpful for calling the xquery transformations.Finally take one more assign activity to call the xquery dynamically like below.


In the above assign activity i have passed the $dynaXQ in the Expression and browsed Version.xq .Once you browsed the Version xqery you will able to see the bind variables.

Use this below xml data when testing your proxy service.
<Route>
<element1>hi</element1>
<element2>My</element2>
<Operation>Operation1</Operation>
</Route>

Please find the jar for the sample code below.
https://drive.google.com/open?id=0B8cpEjk4gP0GM1l0dENtOXJNQUU&authuser=0

No comments:

Post a Comment