WSO2 ESB 4.8.0 Proxy service transcoding iso to utf-8 - encoding

Context:
I use wso2esb 4.8.0.
I have proxy service:
<?xml version="1.0" encoding="UTF-8"?>
<proxy xmlns="http://ws.apache.org/ns/synapse"
name="eProxy"
transports="https"
statistics="disable"
trace="disable"
startOnLoad="true">
<target>
<inSequence>
</inSequence>
<outSequence>
<send/>
</outSequence>
<endpoint>
<address uri="http://10.24.74.53:8088/xxxService?WSDL"/>
</endpoint>
</target>
<publishWSDL uri="file://wso2esb-4.8.0/repository/mcc/resources/xxx.wsdl"/>
<description/>
</proxy>
Problem:
xxxService response is encoding in iso-8859 and I want to transform this response to utf-8
My first approch:
I use xslt mediator :
<?xml version="1.0" encoding="UTF-8"?>
<xsl:stylesheet version="1.0"
xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:output encoding="UTF-8" />
<xsl:template match="/">
<result>
<xsl:value-of select="." />
</result>
</xsl:template>
</xsl:stylesheet>
but I have error
ERROR NativeWorkerPool uncaught exception java.lang.stackoverflowerror com.sun.org.apache.xerces.internal.impl.XMLEntityScanner.scanName(XMLEntityScanner.java:726)
My second approch:
I set property in out Sequence:
<property name='CHARACTER_SET_ENCODING' scope='Axis2' value='UTF-8'/>
but I have error
ERROR NativeWorkerPool uncaught exception java.lang.stackoverflowerror com.sun.org.apache.xerces.internal.impl.XMLEntityScanner.scanName(XMLEntityScanner.java:726)
My last approch:
I write custom mediator but I dont know how chang SoapEnvelope or SoapBody encoding
thinks for your Help.

To change encoding and content type, look at ContentType and messageType properties : http://docs.wso2.org/display/ESB480/Generic+Properties
Sample value : text/xml; charset=ISO-8859-1

Related

how to update soap response namespace value with wso2 ei

I have a proxy service to expose a soap api on wso2 ei, and i need to update the namespace value of the soap response with my proxy service and return another namespace value.
I have tried with the enrich mediator as follows inside the outsequence.
<property name="namespace"
scope="default"
type="STRING"
value="http://tempuri-updated.org/"/>
<enrich>
<source clone="false" property="namespace" type="property"/>
<target xmlns:ser="http://services.samples"
xmlns:ns="http://org.apache.synapse/xsd"
xpath="namespace-uri($body/*)/text()"/>
</enrich>
I get this error.
ERROR - EnrichMediator Invalid Target object to be enrich.
my actual soap response is as follows
<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>
<AddResponse xmlns="http://tempuri.org/">
<AddResult>12</AddResult>
</AddResponse>
</soap:Body>
</soap:Envelope>
my expected output as follows
<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>
<AddResponse xmlns="http://tempuri-updated.org/">
<AddResult>12</AddResult>
</AddResponse>
</soap:Body>
</soap:Envelope>
All your feedbacks are welcome
This cannot be done with the enrich mediator. Because in the code related to enrich mediator target handling [1], the parsed result of an xpath expression should be one of SOAPHeaderImpl, OMElement, OMText or OMAttribute. Since namespace-uri() is just returning a string value, the target to be enriched is becoming invalid. As an alternative to this use case, we can do an XSLT transformation using the XSLT mediator. Following is a sample XSL style sheet I tried.
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:template match="#* | comment() | processing-instruction()">
<xsl:copy/>
</xsl:template>
<xsl:template match="*">
<xsl:element name="{local-name()}"
namespace="http://tempuri-updated.org/">
<xsl:apply-templates select="#* | node()"/>
</xsl:element>
</xsl:template>
We can refer this style sheet in the XSLT mediator before sending the response out from the EI. The new namespace will be added to the body.
Try this.
http://codertechblog.com/wso2-change-payload-soap-envelope-namespace/
<sequence name="seTestChangeNamespace" trace="disable" xmlns="http://ws.apache.org/ns/synapse">
(...)
<enrich>
<source type="body"/>
<target type="property" property="INPUT_MESSAGE"/>
</enrich>
<enrich>
<source type="inline">
<myns:Envelope xmlns:myns="http://schemas.xmlsoap.org/soap/envelope/">
<myns:Body/>
</myns:Envelope>
</source>
<target type="envelope"/>
</enrich>
<enrich>
<source type="property" property="INPUT_MESSAGE"/>
<target type="body"/>
</enrich>
(...)
</sequence>

WSO2 ESB - soap envelope that is automatically added is causing issues

I'm exploring WSO2 ESB and have hit an issue. I am using a simple pass through proxy to post XML data from SAP (or Postman, to test) which then gets forwarded to a REST API - should be easy!
When I POST direct to the REST API (not through ESB), it works fine.(200, OK)
But WSO2 ESB is adding a SOAP Envelope automatically, which the REST API will not accept. I've tried various approaches to remove the automatically added SOAP envelope, with no success. Tried XSLT transform, POX format, Enrich mediator etc., every suggestion I could find.
(I can remove envelope element using XSLT if it is sent as part of the body, but not the one WSO2 adds in)
I can access the body, without SOAP envelope, using :
<property name="body" expression="$body/*[1]" type="OM"/>
but am not sure how to forward this to the API.
Any ideas how to stop this envelope being added in the first place in WSO2 ESB, or on how to remove it?
I used the xslt code from this answer, which works fine when I include the SOAP tags in the body, but has no effect on the SOAP envelope that seems to get automatically added in WSO2 (except to give the error, below).
I tried different variations of the line:
<xsl:apply-templates select="soap:Envelope/soap:Body/*"/>
such as
<xsl:apply-templates select="soap:Envelope/*"/>
<xsl:apply-templates select="/*"/>
this is an error I see in the ESB log:
Unable to perform XSLT transformation using : Value {name ='null', keyValue ='discountPayment'} against source XPath : s11:Body/child::[position()=1] | s12:Body/child::[position()=1] reason : Unable to create an OMElement using XSLT result
I am pretty new to WSO2 ESB, and have not used XSLT before, so may be some very basic mistake in my approach....
here is my proxy xml, and the XSLT "removeSOAP":
<?xml version="1.0" encoding="UTF-8"?>
<proxy name="APIServer" startOnLoad="true" trace="disable"
transports="https http" xmlns="http://ws.apache.org/ns/synapse">
<target>
<inSequence>
<log level="full">
<property name="FirstLog" value="APITest LOG...."/>
<property name="payload" expression="$body/*[1]" type="OM"/>
</log>
<xslt key="removeSOAP"/>
<log level="full">
<property name="SecondLog" value="after xslt...."/>
</log>
<property name="messageType" scope="axis2" type="STRING" value="application/xml"/>
<send>
<endpoint name="endpoint_urn_uuid_xxxxxx">
<address trace="disable" uri="http://myAPIendpoint " />
</endpoint>
</send>
</inSequence>
<outSequence>
<log level="full"/>
<send/>
</outSequence>
<faultSequence/>
</target>
</proxy>
<?xml version="1.0" encoding="UTF-8"?>
<localEntry key="removeSOAP" xmlns="http://ws.apache.org/ns/synapse">
<xsl:stylesheet version="1.0"
xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
xmlns:soap="http://www.w3.org/2003/05/soap-envelope"
xmlns:m="http://www.example.org/stock">
<xsl:template match="/">
<xsl:apply-templates select="soap:Envelope/soap:Body/*"/>
</xsl:template>
<xsl:template match="#*|node()">
<xsl:copy>
<xsl:apply-templates select="#*|node()"/>
</xsl:copy>
</xsl:template>
</xsl:stylesheet>
</localEntry>
A colleague figured this out today, I post the answer here incase it helps someone in the future:
in the proxy service, before send, add the line
<property name="DISABLE_CHUNKING" value="true" scope="axis2"/>
then it works.
No need for the XSLT transform that is shown above, just this line fixes it.
if your backend it´s an API better you can use the http endpoint https://docs.wso2.com/display/ESB500/HTTP+Endpoint:
<send>
<endpoint>
<http method="POST"
uri-template="http://your.backend.endpoint.org/"/>
</endpoint>
</send>

org.apache.axis2.AxisFault: Transport error: 415 Error: Unsupported Media Type

I have created a proxy service in wso2, while try accessing the proxy service it shows error as Unsupported Media Type, but I have set Content-Type: application/xml .payload is in xml format, so am setting it to application/xml in the source view ,still am getting the same error, Please help me to resolve this issue
**Proxy Service:**
<?xml version="1.0" encoding="UTF-8"?>
<proxy xmlns="http://ws.apache.org/ns/synapse"
name="test"
transports="http,https"
statistics="enable"
trace="enable"
startOnLoad="true">
<target>
<outSequence>
<property name="Content-Type" value="application/xml"/>
<send/>
</outSequence>
<endpoint>
<address uri="http://192.35.72.369:8080/ESB_Services/DRAM/service/CreateCustomer"/>
</endpoint>
</target>
<description/>
</proxy>
**Payload:**
<customer>
<name>admin</name>
<email>admin#gmail.com</email>
<mobile_number>9904324234</mobile_number>
<address>Bangalore</address>
<zipcode>574515</zipcode>
</customer>
**ERROR:**
<TryitProxyError h:status="SOAP envelope error" xmlns:h="http://wso2.org/ns/TryitProxy">org.apache.axis2.AxisFault: Transport error: 415 Error: Unsupported Media Type</TryitProxyError>
When you need to choose the appropriate messageFormatter, used to format a message going out from the ESB, you use the property 'messageType' : <property name="messageType" value="application/xml" scope="axis2" />

wso2 esb change soap namespace prefix

I have a proxy service on my wso2esb and a response like this:
<soap:Envelope xmlns:soap="http://schemas.xmlsoap.org/soap/envelope/">
<soap:Body>
..........
</soap:Body>
</soap:Envelope>
Does wso2esb have any configurable place where I can change the soap prefix? I need a result like this:
<soapenv:Envelope xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/">
<soapenv:Body>
..........
</soapenv:Body>
</soapenv:Envelope>
You should'nt care about the name of the namespace, but if you really need that, you can for exemple use enrich mediator to : Save the body, change soap envelope, restore the body
<proxy xmlns="http://ws.apache.org/ns/synapse"
name="TestSOF"
transports="http"
startOnLoad="true"
trace="disable">
<description/>
<target endpoint="ProductEngineServiceMock1">
<outSequence>
<enrich>
<source type="body"/>
<target type="property" property="INPUT_MESSAGE"/>
</enrich>
<enrich>
<source type="inline">
<myns:Envelope xmlns:myns="http://schemas.xmlsoap.org/soap/envelope/">
<myns:Body/>
</myns:Envelope>
</source>
<target type="envelope"/>
</enrich>
<enrich>
<source type="property" property="INPUT_MESSAGE"/>
<target type="body"/>
</enrich>
<send/>
</outSequence>
</target>
</proxy>

WSO2 ESB adding prefix to header

I try to use the WSO2 ESB with the SAP Solution Manager Webservice as an endpoint.
For sending a message to the Webservice I need to modify the SOAP Header.
While searching with google I found out that I could use the Enrich Mediator for this. But I couldn't find an example how to add the prefix to the header.
What I have is this:
<?xml version='1.0' encoding='utf-8'?>
<soapenv:Envelope xmlns:soapenv="http://www.w3.org/2003/05/soap-envelope">
<soapenv:Body>
<urn:ReadCompleteIncident>
<IncidentGuid>xxxxx</IncidentGuid>
<SystemGuid>xxx</SystemGuid>
</urn:ReadCompleteIncident>
</soapenv:Body>
</soapenv:Envelope>
But I get an error because the ESB doesn't know the prefix "urn:". So I have to add "xmlns:urn="urn:sap-com:document:sap:soap:functions:mc-style"" to the Header for getting this:
<?xml version='1.0' encoding='utf-8'?>
<soapenv:Envelope xmlns:soapenv="http://www.w3.org/2003/05/soap-envelope" xmlns:urn="urn:sap-com:document:sap:soap:functions:mc-style">
<soapenv:Body>
<urn:ReadCompleteIncident>
<IncidentGuid>xxxxx</IncidentGuid>
<SystemGuid>xxx</SystemGuid>
</urn:ReadCompleteIncident>
</soapenv:Body>
</soapenv:Envelope>
How can I do this with the Enrich Mediator? Or is there another solution?
Thank you :)
You can use the Header mediator of WSO2 ESB to achieve your requirement.
<header name="Action" value="urn:ReadCompleteIncident"/>
You can refer this link to find more information.
http://docs.wso2.org/wiki/display/ESB460/Header+Mediator
I solved this problem with Enrich Mediator. For example, here is my proxy.
Input message to ESB:
<soap:Envelope xmlns:soap="http://www.w3.org/2003/05/soap-envelope">
<soap:Header/>
<soap:Body>
<content>Message content</content>
</soap:Body>
</soap:Envelope>
Required Input message to SAP PI:
<soapenv:Envelope xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/" xmlns:urn="urn:xxxx">
<soapenv:Header/>
<soapenv:Body>
<urn:xxxx>
<content>Message content</content>
</urn:xxxx>
</soapenv:Body>
</soapenv:Envelope>
Solution:
<proxy xmlns="http://ws.apache.org/ns/synapse"
name="WSO2toSAP"
transports="https,http"
statistics="disable"
trace="disable"
startOnLoad="true">
<target>
<inSequence>
<property name="OUT_ONLY" value="true" scope="default" type="STRING"/>
<property name="FORCE_SC_ACCEPTED"
value="true"
scope="axis2"
type="STRING"/>
<log level="full"/>
<enrich>
<source type="body" clone="true"/>
<target type="property" property="INPUT_MESSAGE"/>
</enrich>
<enrich>
<source type="inline" clone="true">
<soapenv:Envelope xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/">
<soapenv:Body/>
</soapenv:Envelope>
</source>
<target type="envelope"/>
</enrich>
<enrich>
<source type="inline" clone="true">
<urn:xxxx xmlns:urn="urn:xxxx"/>
</source>
<target type="body"/>
</enrich>
<enrich>
<source type="property" clone="true" property="INPUT_MESSAGE"/>
<target type="body" action="child"/>
</enrich>
<log level="full"/>
<send>
<endpoint key="WSO2toSAP_endpoint"/>
</send>
</inSequence>
</target>
<description/>
</proxy>
I hope, that I help you :)
I think there are multiple ways you can solve this problem -
payloadFactory mediator to manipulate the request or response.
using script mediator - check this page http://abeykoon.blogspot.com/2013/03/encoding-and-decoding-xml-using-wso2-esb.html#comment-form for more details on how to use the script. As you can see, the blogger is generating the request using payloadFactory and then manipulate it using the scripts to get the desired effect.
If I find time, I will try to build a quick solution for you using the scripts.
All the best..