WSO2: Enriching a OM property node value - wso2

I have an empty OM property like so:
<property description="empty extra_data" name="extra_data" scope="default">
<extra_data xmlns=""/>
</property>
Later on, I want to add data to this XML structure.
First enriching – adding the child element works fine:
<enrich description="set URL child in extra data">
<source clone="true" type="inline">
<url />
</source>
<target action="child" xpath="$ctx:extra_data"/>
</enrich>
Next, I want to set the URL that is stored in another property ("url").
I've tried it like that but it doesn't work (invalid target):
<enrich description="set url" xmlns:ns="http://ws.apache.org/ns/synapse">
<source clone="true" property="url" type="property"/>
<target xpath="$ctx:extra_data//ns:url/text()"/>
</enrich>
Can anyone help me with that? :)

I found this solution. Set the XML tag and its content in a property and append it as a new child element.
<property description="url xml tag" expression="fn:concat('<url>', $ctx:url, '</url>')" name="url_xml" scope="default" type="OM"/>
<enrich description="set url child in extra data">
<source clone="true" property="url_xml" type="property"/>
<target action="child" property="extra_data" type="property"/>
</enrich>
I still would've liked to replace or set a value inside a node, but that works for now...

Related

Enrich mediator add payload wso2

I used the enrich mediator to add a payload containing the name and totalnote of students
my problem that i want to replace the values ​​with the property
here is my code
<property expression="get-property('uri.var.nom')" name="uri.var.nom" scope="default" type="STRING"/>
<property expression="get-property('totalnote')" name="totalnote" scope="default" type="STRING"/>
<enrich>
<source clone="true" type="inline">
{"nom":"" ,
"note":""}
</source>
<target action="child" xpath="json-eval($)"/>
</enrich>
<enrich>
<source clone="true" property="uri.var.nom" type="property"/>
<target action="replace" xpath="json-eval($.etudiants.nom)"/>
</enrich>
<enrich>
<source clone="true" property="totalnote" type="property"/>
<target action="replace" xpath="json-eval($.etudiants.note)"/>
</enrich>
<respond/>
it doesn't work I always receive empty
{ "etudiants": { "nom": "", "note": "" }
You are placing the JSON structure at the root. As a child of $. But your structure does not contain etudiants, therefore the json-eval of $.etudiants.nom won't work.
The enrich itself works, as shown by #ycr but the message structure you assume to have is incorrect. Try logging the body after the first enrich to see what your payload looks like at that point.
Depending on your payload before the enrich try something like:
<enrich>
<source clone="true" type="inline">
{"etudiants": {
"nom":"" ,
"note":""
}
</source>
<target action="replace" type="body"/>
</enrich>
Or if you already have the 'etudiants' object maybe try adjusting the json-eval:
<enrich>
<source clone="true" type="inline">
{"nom":"" ,
"note":""}
</source>
<target action="child" xpath="json-eval($.etudiants)"/>
</enrich>
Hope this helps to clarify the situation.
The following seems to work for me. I have hardcoded the property values to test this. Also assuming the Payload before the Enrich is set as { "etudiants": { "nom": "", "note": "" }}. In the following example, I'm sending it in the request.
<?xml version="1.0" encoding="UTF-8"?>
<api context="/HelloWorld" name="HelloWorld" xmlns="http://ws.apache.org/ns/synapse">
<resource methods="POST">
<inSequence>
<property name="uri.var.nom" scope="default" type="STRING" value="nomVal"/>
<property name="totalnote" scope="default" type="STRING" value="20"/>
<enrich>
<source clone="true" property="uri.var.nom" type="property"/>
<target xpath="json-eval($.etudiants.nom)"/>
</enrich>
<enrich>
<source clone="true" property="totalnote" type="property"/>
<target xpath="json-eval($.etudiants.note)"/>
</enrich>
<respond/>
</inSequence>
<outSequence/>
<faultSequence/>
</resource>
</api>
Request
curl --location --request POST 'http://localhost:8290/HelloWorld' \
--header 'Content-Type: application/json' \
--data-raw '{
"etudiants": {
"nom": "",
"note": ""
}
}'
Output
{
"etudiants": {
"nom": "nomVal",
"note": 20
}
}

WSO2 EI new xml tag using Enrich mediator and when xml tag takes dynamically

Is it possible to add new xml tag to xml payload using enrich mediator.
my sample payload -
<courses>
<id>181</id>
<formatted_name>Learning</formatted_name>
<score>0</score>
<status>in_progress</status>
<issued_certificate />
<from_timestamp>1626083705</from_timestamp>
<to_timestamp />
</courses>
New tag would be
<link> www.google.com </link>
I cannot use inline as the source since link is taken dynamically.
So I'm adding new tag to a payload and then property.
<payloadFactory media-type="xml">
<format>
<link xmlns="">$1</link>
</format>
<args>
<arg evaluator="xml" expression="get-property('login_link')"/>
</args>
</payloadFactory>
<property description="Get login link payload" expression="//root/*" name="login_link_xml" scope="default" type="STRING"/>
// get original payload back
<enrich description="Restore original payload">
<source clone="false" property="course_payload" type="property"/>
<target type="body"/>
</enrich>
// assign property as a new node inside the courses
<enrich>
<source clone="true" property="login_link_xml" type="property"/>
<target action="child" type ="custom" xpath="//courses"/>
</enrich>
This gives the same payload after enrich
You can do it in a bit different way. Create your 'tag' as property type OM, using xpath expresion and function: concat, with coded char
<property name="my_link" value="devintegra.com" scope="default" type="STRING"/>
<property name="linkNode"
type="OM"
expression="concat('<link>',get-property('my_link'),'</link>')"
scope="default" />
And with that property you can enrich your body:
<enrich>
<source type="property" clone="true" property="linkNode"/>
<target action="child" xpath="//courses"/>
</enrich>
That should work as you expect.

wso2 esb inject few values after xslt transformation

I am reading some values from source table and writing to a target table.Since the fields are different in names and some values , i am using XSLT mediator in WSO2 ESB.
After the xslt mediator , i want to inject few more values into the payload.Say some variables which i have previously store. I cant do it xslt because these values are in some variables.
So below is my code.What should be the code the dashed lines?
<enrich>
<source clone="true" property="SOURCE_TABLE_PAYLOAD" type="property"/>
<target type="body"/>
</enrich>
<xslt key="gov:/bcogc/transformation/SourcetoTargetTransformation.xslt"/>
----------------ADD SOME MORE VALUES HERE to the payload------------------
<header name="Action" scope="default" value="urn:inserttotargettable"/>
<call>
<endpoint key="gov:/endpoints/INSERT_DataService_EP.xml"/>
</call>
Please throw some lights
You can again use an enrich mediator for example ,
<property name="orderID" scope="default" description="orderID">
<orderID xmlns="">2</orderID>
</property>
<enrich>
<source clone="true" xpath="$ctx:orderID"/>
<target action="sibling" xpath="//orders"/>
</enrich>
Here the orderID property is defined , so now you can add that property as a sibling with you request coming out of XSLT, so the request will look like below after enriching
<orders>
<order>
<price>50.00</price>
<quantity>500</quantity>
<symbol>IBM</symbol>
<comment>REF 10053</comment>
</order>
<order>
<price>18.00</price>
<quantity>500</quantity>
<symbol>MSFT</symbol>
<comment>ref 20088398289</comment>
</order>
</orders>
<orderID>2</OrderID>

How can I obtain XML empty tag when I obtain null value from a DSS service into an ESB application generating an XML document?

I am absolutly new in WSO2 project and I have the following problem. I am working on an Enterprise Intergrator project (that involves ESB and DSS components).
I am generating an XML document starting from data contained into some database tables. These data are aggregate using a pretty complex logic.
My problem is the following one:
into my ESB flow I have these chained enrich mediator used a create this section of the final XML document, this is the code:
<!-- add placeholders for additional <sampleid> and <provenance> tags -->
<enrich>
<source clone="true" type="inline">
<parent xmlns="http://ws.wso2.org/dataservice">
<sampleid>[pgrfas.prov_sid]</sampleid>
<provenance>[pgrfas.provenance]</provenance>
</parent>
</source>
<target property="moreValues" type="property"/>
</enrich>
<!-- Copy values for <sampleid> and <provenance> tags -->
<enrich>
<source clone="true" xmlns:ns="http://org.apache.synapse/xsd" xpath="$ctx:moreValues/child::*"/>
<target action="child" xmlns:ds="http://ws.wso2.org/dataservice" xmlns:ns="http://org.apache.synapse/xsd" xpath="$ctx:serviceCall//ds:register/ds:acquisition"/>
</enrich>
<enrich>
<source clone="true" xmlns:ds="http://ws.wso2.org/dataservice" xmlns:ns="http://org.apache.synapse/xsd" xpath="$ctx:sampleData//ds:Sample/ds:prov_sid/text()"/>
<target action="child" xmlns:ds="http://ws.wso2.org/dataservice" xmlns:ns="http://org.apache.synapse/xsd" xpath="$ctx:serviceCall//ds:register/ds:acquisition/ds:sampleid/text()"/>
</enrich>
As you can see in the first mediator definition I am defining 2 XML element ( and ) by:
<parent xmlns="http://ws.wso2.org/dataservice">
<sampleid>[pgrfas.prov_sid]</sampleid>
<provenance>[pgrfas.provenance]</provenance>
</parent>
Ad I am define 2 placeholder that should be replace with the data obtained from the DB by this chained following mediators:
<enrich>
<source clone="true" xmlns:ds="http://ws.wso2.org/dataservice" xmlns:ns="http://org.apache.synapse/xsd" xpath="$ctx:sampleData//ds:Sample/ds:prov_sid/text()"/>
<target action="child" xmlns:ds="http://ws.wso2.org/dataservice" xmlns:ns="http://org.apache.synapse/xsd" xpath="$ctx:serviceCall//ds:register/ds:acquisition/ds:sampleid/text()"/>
</enrich>
<enrich>
<source clone="true" xmlns:ds="http://ws.wso2.org/dataservice" xmlns:ns="http://org.apache.synapse/xsd" xpath="$ctx:sampleData//ds:Sample/ds:provenance"/>
<target xmlns:ds="http://ws.wso2.org/dataservice" xmlns:ns="http://org.apache.synapse/xsd" xpath="$ctx:serviceCall//ds:register/ds:acquisition/ds:provenance"/>
</enrich>
This is the related section in the final XML document generated by this EXB application:
<sampleid>coll_sid-001</sampleid>
<missid>coll_miss_id-001</missid>
Where coll_sid-001 and coll_miss_id-001 are retrieved from the database by the DSS service (previously putted into the $ctx:sampleData property).
If into the database table on which the DSS query is perfromed there are the value related to the XML and field it works fine and I obtain the previous output.
If this table contains null value for these fields I obtain this output into the generated XML:
<sampleid>[pgrfas.coll_sid]</sampleid>
<missid>[pgrfas.coll_miss_id]</missid>
As you can see, if it can't find the related value on the DB table it put the defined placeholder into the generated XML.
This is not good for my purpose. If into the DB table are present null values I want obtain an empty tag into my generated XML document, something like this:
<sampleid />
<missid />
How can I fix this issue? Exist some simple workaround to obtain empty tag in this situation?
Try it create your enrich in this way
<enrich>
<source clone="true" type="inline">
<parent xmlns="http://ws.wso2.org/dataservice">
<sampleid/>
<provenance/>
</parent>
</source>
<target property="moreValues" type="property"/>
</enrich>

How to insert soap:Body content as a child to another tag

I have the following soap:body
<soapenv:Body>
<Message>
<Context>
<id>10</id>
<subject>sub10</subject>
<body>body10</body>
</Context>
</Message>
</soapenv:Body>
But I need to insert the content inside <SendMessageRequest> tag before sending to a request:
<soapenv:Body>
<SendMessageRequest>
<Message>
<Context>
<id>10</id>
<subject>sub10</subject>
<body>body10</body>
</Context>
</Message>
</SendMessageRequest>
</soapenv:Body>
I'm using the Enrich Mediator, but not figured out how to do this...
Here the code I'm trying:
<enrich>
<source type="body"/>
<target action="child" type="custom" xpath="SendMessageRequest"/>
</enrich>
You can't directly add an intermediate element. That is one that wraps your current content. Instead you can store your content-to-be-wrapped in a property. Note the use of the $body xpath variable (courtesy of the SynapseXPath class), which refers to the soap body element regardless of used soap version.
<property name="payload" expression="$body/*[1]" type="OM"/>
Then use the PayloadFactory mediator to construct your new request stub:
<payloadFactory>
<format>
<SendMessageRequest xmlns=""/>
</format>
<args/>
</payloadFactory>
Subsequently you can enrich your former content into the newly created payload.
<enrich>
<source clone="true" property="payload" type="property"/>
<target action="child" type="custom" xpath="$body/SendMessageRequest"/>
</enrich>