I want remove xml declaration from wso response created by payload mediator (post method).
<?xml version='1.0' encoding='UTF-8'?>
<soapenv:Envelope xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/" xmlns:mgod="MgOdinCToCrm" xmlns:mgex="MgExchange">
<soapenv:Body>
<m:getQuote xmlns:m="http://services.samples/xsd">
<m:request>
<m:symbol/>
</m:request>
</m:getQuote>
</soapenv:Body>
</soapenv:Envelope>
I try use xslt and js mediators to modify response, but it isn't help. This mediator can modify content only in body tag. May be someone faced with this problem
Try with setting messageType as follows.
<property name="messageType" scope="axis2" type="STRING" value="application/xml"/>
Related
I'm send soap reqest to microservice and in respond I get this.
<soapenv:Envelope xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/">
<soapenv:Body>
<soapenv:Fault>
<faultcode xmlns:SOAP-ENV="http://schemas.xmlsoap.org/soap/envelope/">SOAP-ENV:Client</faultcode>
<faultstring>An error was detected in the Web Service request. (10894)</faultstring>
<detail>
<ns1:FaultDetail xmlns:ns1="urn:soap-fault:details">
<errorMessage>Error in SOAP Envelope: Content length must be specified. (10913)</errorMessage>
<requestID>----</requestID>
</ns1:FaultDetail>
</detail>
</soapenv:Fault>
</soapenv:Body>
</soapenv:Envelope>
I create my soap envelope in payloadFactory.
<payloadFactory description="Set ARGS for CALL" media-type="xml">
<format>
<soapenv:Envelope xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/" xmlns:urn="urn:xyz:zyz">
<soapenv:Header/>
<soapenv:Body>
...
</soapenv:Body>
</soapenv:Envelope>
</format>
<args>
...
</args>
</payloadFactory>
Next I send this to microservice. Micro service work on SOAP 1.1. I'm don't attach content lenght because I do not know how.
After the PL factory and before sending the request try setting the following properties.
<property name="DISABLE_CHUNKING" value="true" scope="axis2" />
<property name="messageType" value="text/xml" scope="axis2" type="STRING"/>
I am working on conditional router in wso2 esb and my scenario is as follows.
I extracted studentno in payload and wanted to perform conditional router on the top of that but this is working for header and query params and not for query variables or a value extracted from payload. I tried for the solution but I got switch-case as a solution. Is this is a limitation in conditional router that works only with header and params? If no please provide your inputs on the condition in conditional router.
Thanks in advance.
There are two types to achieve your requirement. You should be able to use either the type soap [2] or the type property [1] to route based on the payload content. Refer to the sample below. The other available types can be found in the documentation [3].
<?xml version="1.0" encoding="UTF-8"?>
<proxy xmlns="http://ws.apache.org/ns/synapse"
name="conditionalRouter"
startOnLoad="true"
statistics="disable"
trace="disable"
transports="http,https">
<target>
<inSequence>
<property expression="$body//symbol" name="requestProperty"/>
<log level="custom">
<property expression="$body//symbol" name="requestProperty"/>
</log>
<conditionalRouter continueAfter="false">
<conditionalRoute breakRoute="false">
<condition>
<match regex="WSO2.*" source="//symbol" type="soap"/>
</condition>
<target sequence="cnd1_seq"/>
</conditionalRoute>
<conditionalRoute breakRoute="false">
<condition>
<match regex="IBM.*" source="requestProperty" type="property"/>
</condition>
<target sequence="cnd2_seq"/>
</conditionalRoute>
</conditionalRouter>
</inSequence>
</target>
<description/>
</proxy>
request 1
<soapenv:Envelope xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/">
<soapenv:Header/>
<soapenv:Body>
<request>
<symbol>WSO2</symbol>
</request>
</soapenv:Body>
</soapenv:Envelope>
request 2
<soapenv:Envelope xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/">
<soapenv:Header/>
<soapenv:Body>
<request>
<symbol>WSO2</symbol>
</request>
</soapenv:Body>
</soapenv:Envelope>
Note
The Conditional Router Mediator is removed from the EI 6.5.0 version onwards [4]. Therefore if you have already developed your mediation using the switch case mediator, better to use the same since it would be easier for you if you decide to migrate to a new EI version.
[1]-https://github.com/wso2/wso2-synapse/blob/v2.1.7-wso2v111/modules/commons/src/main/java/org/apache/synapse/commons/evaluators/config/TextProcessingEvaluatorFactory.java#L60
[2]-https://github.com/wso2/wso2-synapse/blob/v2.1.7-wso2v111/modules/commons/src/main/java/org/apache/synapse/commons/evaluators/config/TextProcessingEvaluatorFactory.java#L66
[3]-https://docs.wso2.com/display/EI620/Sample+157%3A+Conditional+Router+for+Routing+Messages+based+on+HTTP+URL%2C+HTTP+Headers+and+Query+Parameters
[4]-https://docs.wso2.com/display/EI650/About+this+Release
I need to create Soap Operation GetFile to respond with file content and additional tags using MTOM (reponse Content-Type multipart/related):
<Response>
<file>
<id>1</id>
<name>Filename.pdf</name>
<content>
<xop:Include href="cid:test" xmlns:xop="http://www.w3.org/2004/08/xop/include"/>
</content>
</file>
</Response>
I have proxy which calls external service to get file content and then I generate payload using PayloadFactory mediator ($body/* in this case is file binary content from external service, id and name are hardcoded for simplicity):
<payloadFactory media-type="xml">
<format>
<Response>
<file>
<id>$1</id>
<name>$2</name>
<content>$3</content>
</file>
</Response>
</format>
<args>
<arg value="1"/>
<arg value="fileName.pdf"/>
<arg evaluator="xml"
expression="$body/*"/>
</args>
</payloadFactory>
<property name="enableMTOM" scope="axis2" type="STRING" value="true"/>
<respond/>
In response I get:
<soapenv:Envelope xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/">
<soapenv:Body>
<Response xmlns="http://ws.apache.org/ns/synapse">
<file>
<id>1</id>
<name>fileName.pdf</name>
<content>base64content</content>
</file>
</Response>
</soapenv:Body>
</soapenv:Envelope>
If I remove that payloadFactory then I get correct multipart/related response, so enableMTOM property works (but I need additional custom tags):
<soapenv:Envelope xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/">
<soapenv:Body>
<ns:binary xmlns:ns="http://ws.apache.org/commons/ns/payload">
<xop:Include href="cid:1" xmlns:xop="http://www.w3.org/2004/08/xop/include"/>
</ns:binary>
</soapenv:Body>
</soapenv:Envelope>
Is custom mediator with messageContext.addAttachment only solution in this case? And whats best practice in such case - save received file content locally on server and then use it as attachment?
If you are constructing the message payload using a Payload factory mediator, and expecting to send the response as "multipart/form-data", you need to set the message type of the response after the Payload factory mediator. You can use the following property to set the message type of the response.
<property name="messageType" value="multipart/form-data" scope="axis2"/>
Furthermore, when we manipulate the file content using the Payload factory mediator, the message context gets built inside the Payload factory mediator and returned as a base64 encoded value. In order to decode the content, you need to add the following property to your proxy configuration.
<property name="DECODE_MULTIPART_DATA" value="true" scope="axis2" action="set" type="BOOLEAN"/>
Please refer to the latest WSO2 documentation on MTOM and SwA Optimizations and Request/Response Correlation for more details on this.
In a content-aware mediation scenario (where the message gets built), you can use the following property to decode the multipart message that is being sent to the backend. Otherwise, the outgoing message will be in encoded form.
hopefully someone can point out the blindingly obvious to me - I want to perform a few simple translations on a soap payload before I send to a backend service - crucially, I need access to all the soap-headers delivered in the original payload.
My naive(?) thinking was to simply set the source attribute for the <xslt> mediator to "/" as Im aware by default it will start from the first child of the <body>, and I really need access to the headers.
WSO2 returns a "The evaluation of the XPath expression / did not result in an OMNode" error.
Are there one or more WSO2/xpath interworking quirks that Ive missed in the literature? Any pointers gratefully recieved, thanks
As Tishan mentioned you can use $header synapse xpath variable to access soap headers in message context. But it's bit tricky when it comes to xslt mediator. You cannot directly access message context values inside xslt stylesheet. But it is possible to pass these values as parameters and use in transformation. Let's see how we can achieve this.
Below is how account.xslt file looks like. Please note that there are two parameters called PARAM_SSN and PARAM_ACCT_NO used to assign value for <ssn></ssn> and <accountNumber></accountNumber>
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:param name="PARAM_SSN"></xsl:param>
<xsl:param name="PARAM_ACCT_NO"></xsl:param>
<xsl:template match="/">
<account xmlns="http://services.samples">
<ssn>
<xsl:value-of select="$PARAM_SSN"></xsl:value-of>
</ssn>
<accountNumber>
<xsl:value-of select="$PARAM_ACCT_NO"></xsl:value-of>
</accountNumber>
<accountHolder>
<xsl:value-of select="//name"></xsl:value-of>
</accountHolder>
</account>
</xsl:template>
</xsl:stylesheet>
Above file saved in registry of WSO2 ESB under /_system/governance/transform/account.xslt
Next is sample proxy which do the transformation with account.xslt
<?xml version="1.0" encoding="UTF-8"?>
<proxy xmlns="http://ws.apache.org/ns/synapse"
name="TransformExample"
transports="https,http"
statistics="disable"
trace="disable"
startOnLoad="true">
<target>
<inSequence>
<xslt key="gov:/transform/account.xslt">
<property name="PARAM_SSN" expression="$header/seccode"/>
<property name="PARAM_ACCT_NO" expression="$trp:acctNo"/>
</xslt>
<log level="custom">
<property name="Transformed Payload" expression="$body"/>
</log>
</inSequence>
<outSequence>
<send/>
</outSequence>
</target>
<description/>
</proxy>
Here you could see that inside <xslt> mediator, I am passing values for two parameters define in xslt by accessing message context. Value for PARAM_SSN taken from soap header and value for PARAM_ACCT_NO taken from transport header. This proxy service called by soapUI with below payload.
<soapenv:Envelope xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/">
<soapenv:Header>
<seccode>987654321</seccode>
</soapenv:Header>
<soapenv:Body>
<request>
<name>Indika Sampath</name>
</request>
</soapenv:Body>
</soapenv:Envelope>
Also I am sending acctNo as transport header along with request. Once this hit the proxy, you could see transformed output log as below in console.
[2016-01-09 07:19:02,146] INFO - LogMediator Transformed Payload = <soapenv:Body xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/">
<account xmlns="http://services.samples"><ssn>987654321</ssn><accountNumber>123456789</accountNumber><accountHolder>Indika Sampath</accountHolder></account>
</soapenv:Body>
Hope this would resolve your problem.
Cheers!
You can access SOAP headers using Synapse Xpath Variable $header in your source xpath (Ex:$header/wsa:To). Hope this helps!!
Good day!
I only recently began to study the ESB bus. I need to convert the incoming SOAP message in the HTTP request with Content-Type: application/x-www-form-urlencoded.
I have created a Proxy Service, Custom Mediator 1 in Java, transformed message, how do I pass it to the endpoint and get the answer in Custom Mediator 2?
In the picture I have drawn an example of how to transform the message.
You don't need to write custom mediators, you can transform SOAP to rest calls, sample with a rest service waiting for 2 parameters like
param1=value1¶m2=value2
<!-- prepare data for org.apache.axis2.transport.http.XFormURLEncodedFormatter message formatter -->
<payloadFactory media-type="xml">
<format>
<soapenv:Envelope xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/">
<soapenv:Body>
<root>
<param1>$1</param1>
<param2>$2</param2>
</root>
</soapenv:Body>
</soapenv:Envelope>
</format>
<args>
<arg evaluator="xml" expression="$body/node1/node11/text()"/>
<arg evaluator="xml" expression="$body/node1/node12/text()"/>
</args>
</payloadFactory>
<!-- set output format -->
<property name="messageType" value="application/x-www-form-urlencoded" scope="axis2" type="STRING"/>
<property name="DISABLE_CHUNKING" value="true" scope="axis2" type="STRING"/>
<!-- call the REST endpoint with synch call : response is received in this sequence -->
<call>
<endpoint key="conf:endpoints/MyServiceEndpoint.xml"/>
</call>
<!-- the response is here, transform it has needed -->
<xslt key="myxsl"/>
<!-- send this response to the client -->
<property name="messageType" value="application/soap+xml" scope="axis2" type="STRING"/>
<!-- or test/xml and in this case, don't forget to specify a SOAP Action, below, a sample to specify a blank soapAction : -->
<header name="Action" value=""""/>
<send/>
Sample endpoint conf (with this sample, you need to define a property uri.var.ServiceURL in your sequence) :
<endpoint>
<http method="POST" uri-template="{uri.var.ServiceURL}/Path/2011-10-01"/>
</endpoint>
But if you really need your custom mediators, just replace payloadFactory and xslt mediators with them
Thanks for the reply, I still have to write custom mediator, just a very complex transformation messages
I will give an example how should I transform the message
SOAP message in my Proxy Service, send in custrom mediator
<soap:Envelope xmlns:soap="http://schemas.xmlsoap.org/soap/envelope/"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
xmlns:xsd="http://www.w3.org/2001/XMLSchema">
<soap:Body>
<AddPay xmlns="http://MyTestService">
<!--input dynamic data-->
<fields>
<Items>
<Data>
<Name>Field1</Name>
<Value>11</Value>
</Data>
<Data>
<Name>Field2</Name>
<Value>22</Value>
</Data>
</Items>
</fields>
</AddPay>
</soap:Body>
</soap:Envelope>
The result of the transformation of the mediator
0000035401SM000000970000009700000121
api99 00000990
00000000
BEGIN // <!--input dynamic data-->
FIELD1=11 // Soap data
FIELD2=22 // Soap data
END
BEGIN SIGNATURE
iQBRAwkBAAAD3j2r2NwBAeevAf4nvAG4rGAyAePHkyVKTt7wffzURhOckd3ctgmG
yQkKWkXh3CLpsbrExsllVUBlO6ih8qHozk2uttXApzHXQXoO
=+pch
END SIGNATURE
Request to the HTTP Server
POST /cgi-bin/es/es_pay_check.cgi HTTP/1.0
Content-Type: application/x-www-form-urlencoded
Content-Length: 498
inputmessage=0000035401SM000000970000009700000121%0D%0Aapi99+
+++++++++++00000990%0D%0A++++++++++++++++++++00000000%0ABEGIN%0D%
0FIELD1%11%0FIELD2%220AEND%0D%0ABEGIN+SIGNATURE%0AiQBRAwkBAABCiUs
00dQBATG5AgDHdZ6RYHykL46QBaAvnHYaY4p0pDjgjO4K1Iyj%0D%0AfSBSvCRpS%2
F0EYO9NspuyLeANEQQkkGE%2F37gUxiPqzAgStXjpsAHH%0D%0A%3DvSgb%0AEND+
SIGNATURE
The response from the HTTP Server, pass in custrom mediator to transform into SOAP
0000030301SM000000460000004600000121
0J0005 00064182
00000000
BEGIN
DATE=04.10.2014 12:34:12
ERROR=0
ERRMSG=
FIELD3=33
FIELD4=44
FIELD5=55
END
BEGIN SIGNATURE
iQBRAwkBAAD6tj1BJ10BAYKxAfsHlQsEFnO2k6ry++W8O8AiJuv4gT+ZVCfZHsKk
c0CbZpP/W3vkljG3xNzMLiqjbwkNuIdwR9Dq7gHmH+ZQMhbT
=LOnP
END SIGNATURE
The result in the Proxy service
<s:Envelope xmlns:s="http://schemas.xmlsoap.org/soap/envelope/">
<s:Body>
<AddPayResponse xmlns="http://MyTestService">
<AddPayResult xmlns:i="http://www.w3.org/2001/XMLSchema-instance">
<Data>
<Items>
<!--output dynamic data-->
<Data>
<Name>Field3</Name>
<Value>33</Value>
</Data>
<Data>
<Name>Field4</Name>
<Value>44</Value>
</Data>
<Data>
<Name>Field5</Name>
<Value>55</Value>
</Data>
</Items>
</Data>
<ErrCode>0</ErrCode>
<ErrMsg>Ok</ErrMsg>
</AddPayResult>
</AddPayResponse>
</s:Body>
</s:Envelope>